package com.sihan.framework.etm.controller;

import com.framework.annotation.BusinessLog;
import com.framework.annotation.ParamParser;
import com.framework.exception.AuthException;
import com.framework.model.ApiResult;
import com.framework.mybatis.Condition;
import com.framework.util.WebUtils;
import com.framework.util.crypto.digest.MD5;
import com.framework.util.lang.RegexpUtils;
import com.sihan.framework.etm.common.util.EtmWebUtil;
import com.sihan.framework.etm.common.util.ImgUtils;
import com.sihan.framework.etm.common.websocket.WsSessionManager;
import com.sihan.framework.etm.dto.*;
import com.sihan.framework.etm.entity.Org;
import com.sihan.framework.etm.entity.User;
import com.sihan.framework.etm.enums.FormatImgPre;
import com.sihan.framework.etm.mapper.OrgMapper;
import com.sihan.framework.etm.mapper.UserMapper;
import com.sihan.framework.etm.service.UserService;
import com.sihan.framework.etm.vo.CommonQueryResultVO;
import com.sihan.framework.etm.vo.LoginVO;
import com.sihan.framework.etm.vo.UserVO;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;

import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authz.annotation.RequiresAuthentication;
import org.apache.shiro.session.Session;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import javax.validation.Valid;

import java.util.Collections;

@Api(tags = "用户个人管理")
@RestController
@RequestMapping("/system/v0/user")
public class UserController {

  @Autowired
  private UserService userService;
  
  @Autowired
  private UserMapper userMapper;
  
  @Autowired
  private OrgMapper orgMapper;
  
  @Autowired
  private ImgUtils imgUtils;
  
  @ApiOperation("登录系统")
  @ApiImplicitParams({
      @ApiImplicitParam(name = "username", value = "用户名", dataType = "string", paramType = "form", required = true),
      @ApiImplicitParam(name = "password", value = "密码", dataType = "string", paramType = "form", required = true),
      @ApiImplicitParam(name = "rememberMe", value = "记住我", dataType = "boolean", paramType = "form"),
      @ApiImplicitParam(name = "captcha", value = "验证码", dataType = "string", paramType = "form")
  })
  @PostMapping("/login")
  @BusinessLog("登录系统")
  public ApiResult<?> login(@Valid @ParamParser LoginDTO dto, HttpServletRequest request) throws AuthException {
    //线上开启验证码验证
    //captcha.validate(dto.getCaptcha());
    Subject subject = SecurityUtils.getSubject();
    Session session = subject.getSession();
    String hashId = MD5.getInstance().encode(session.getId() + session.getHost() + request.getHeader("user-agent")).toHex();
    LoginVO loginVo = userService.login(dto.getUsername(), dto.getPassword(), hashId);
    return ApiResult.success(loginVo);
  }


    @ApiOperation("小程序登录系统")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "username", value = "用户名", dataType = "string", paramType = "form", required = true),
            @ApiImplicitParam(name = "password", value = "密码", dataType = "string", paramType = "form", required = true),
            @ApiImplicitParam(name = "rememberMe", value = "记住我", dataType = "boolean", paramType = "form"),
            @ApiImplicitParam(name = "captcha", value = "验证码", dataType = "string", paramType = "form")
    })
    @PostMapping("/wxlogin")
    @BusinessLog("小程序登录系统")
    public ApiResult<?> wxlogin(@Valid @RequestBody @ParamParser LoginDTO dto, HttpServletRequest request) throws AuthException {
        Subject subject = SecurityUtils.getSubject();
        Session session = subject.getSession();
        LoginVO loginVo = userService.wxlogin(dto.getUsername(), dto.getPassword());
        return ApiResult.success(loginVo);
    }

  @ApiOperation("用户注册")
  @ApiImplicitParams({
      @ApiImplicitParam(name = "name", value = "姓名", dataType = "string", paramType = "form", required = true),
      @ApiImplicitParam(name = "username", value = "用户名", dataType = "string", paramType = "form", required = true),
      @ApiImplicitParam(name = "password", value = "密码", dataType = "string", paramType = "form", required = true),
      @ApiImplicitParam(name = "sex", value = "性别", dataType = "boolean", paramType = "form"),
      @ApiImplicitParam(name = "phone", value = "电话号码", dataType = "string", paramType = "form"),
      @ApiImplicitParam(name = "email", value = "邮箱", dataType = "string", paramType = "form")
  })
  @PostMapping("/register")
  @BusinessLog("用户注册")
  public ApiResult<?> register(@Valid RegisterDTO dto) {
    userService.register(dto.getName(), dto.getUsername(), dto.getPassword(), dto.getSex());
    return ApiResult.success();
  }

  @GetMapping("/logout")
  @ApiOperation("退出系统")
  @BusinessLog("退出系统")
  @RequiresAuthentication
  public ApiResult<?> logout(String username) {
      HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
      HttpSession session = request.getSession(false);
      //退出登录 关闭WebSocket连接
      WsSessionManager.removeAndClose(session.getId());
      SecurityUtils.getSubject().logout();
    return ApiResult.success();
  }

  @ApiOperation("获取个人信息")
  @GetMapping("/info")
  @BusinessLog("获取个人信息")
  @RequiresAuthentication
  public ApiResult<?> info() {
   // User user = userService.selectOne(new Condition<>(new User(WebUtils.username(), false)));
   // Set<String> roles = roleService.selectRolesByUsername(WebUtils.username());
   // Set<String> permissions = permissionService.selectPermissionsByRoles(roles);
	User user = userMapper.selectOne(new Condition<>().eq("username", WebUtils.username()).eq("is_delete", 0));
    UserVO userVO = new UserVO();
    BeanUtils.copyProperties(user, userVO);
   // userVO.setPermissions(permissions);
    Org o = orgMapper.selectById(userVO.getOrgId());
    if(null != o) {
    	userVO.setTeam(Collections.singletonList(new CommonQueryResultVO(o.getId(), o.getName())));
        Org country = orgMapper.selectById(o.getParentId());
        if(null != country) {
        	userVO.setCountry(Collections.singletonList(new CommonQueryResultVO(country.getId(), country.getName())));
            Org city = orgMapper.selectById(country.getParentId());
            if(null != city) {
            	userVO.setCity(Collections.singletonList(new CommonQueryResultVO(city.getId(), city.getName())));
            }
        }
    }
    if(!StringUtils.isBlank(userVO.getAvator())) {
    	userVO.setAvator(imgUtils.formatImgPath(FormatImgPre.PRE_AVATOR.getValue()+userVO.getAvator()));
    }
    return ApiResult.success(userVO);
  }

  @ApiOperation("更新个人信息")
  @PostMapping("/info/update")
  @BusinessLog("更新个人信息")
  @RequiresAuthentication
  public ApiResult<?> updateUserInfo(@ApiParam(name = "userIds", value = "个人信息", required = true) @RequestBody @Valid UserInfoDTO dto) {
    User user = new User();
    BeanUtils.copyProperties(dto, user);
    return userService.updateInfo(user) ? ApiResult.success() : ApiResult.fail("更新失败");
  }

  @ApiOperation("修改密码")
  @PostMapping("/password/update")
  @RequiresAuthentication
  public ApiResult<?> updatePassword(@Valid UserUpdatePassDTO dto) {
//    String oldPsd;
//    String newPsd;
//    String suNewPsd;
////    try {
////      //oldPsd = SM2Coder.decode(dto.getOldPassword());
////      //newPsd = SM2Coder.decode(dto.getNewPassword());
////      //suNewPsd = SM2Coder.decode(dto.getSuNewPassword());
////    } catch (IOException e) {
////      e.printStackTrace();
////      throw new BusinessException("未知异常，联系管理员");
////    } catch (DataTamperException e) {
////      e.printStackTrace();
////      throw new BusinessException("数据在传输过程中被恶意篡改，请确保环境是否安全");
////    }
	  String oldPsd = dto.getOldPassword();
	  String newPsd = dto.getNewPassword();
	  String suNewPsd = dto.getSuNewPassword();
    if(!RegexpUtils.isPassword(newPsd) || !RegexpUtils.isPassword(suNewPsd)) {
      return ApiResult.fail("密码只能是8-20位必须符合由大写字母、小写字母、数字、特殊字符至少其中三种组成");
    } else {
      if(!newPsd.equals(suNewPsd)) {
        return ApiResult.fail("新密码和确认密码不一致");
      }
      userService.updatePassword(oldPsd, newPsd);
      logout(WebUtils.username());
      return ApiResult.success();
    }
  }
  
	@ApiOperation("拍照")
	@PostMapping("/update/face")
	@BusinessLog("拍照")
	@RequiresAuthentication
	public ApiResult<?> updateFace(@RequestBody UserVO param) {
		return userService.updateFaceInfo(param.getId(),param.getImg());
	}
	
	@ApiOperation("录入icCard")
	@PostMapping("/update/ic_card")
	@BusinessLog("录入icCard")
	@RequiresAuthentication
	public ApiResult<?> updateIcCard(@RequestBody UserVO param) {
		return userService.updateIcCardInfo(param.getId());
	}
  
  
	@ApiOperation("ICCard识别")
	@GetMapping("/validate/operator/ic-card")
	@BusinessLog("ICCard识别")
	@RequiresAuthentication
	public ApiResult<?> operatorICCardValidate(
			@ApiParam(name = "openDoor", value ="是否开门（true：开门，false：不开门）", required = false) 
			@RequestParam(name="openDoor",required = false) Boolean openDoor) {
		UserVO param = new UserVO();
		if(null != openDoor) {
			param.setOpenDoor(openDoor);
		}
		
		return userService.getOperatorUserIdFromHardware(1,param);
	}
	
	@ApiOperation("人脸识别")
	@PostMapping("/validate/operator/face")
	@BusinessLog("人脸识别")
	@RequiresAuthentication
	public ApiResult<?> operatorFaceValidate(@RequestBody UserVO param) {
		return userService.getOperatorUserIdFromHardware(2,param);
	}
	
	
	@ApiOperation("检查是否登录")
	@PostMapping("/validate/login")
	@BusinessLog("检查是否登录")
	@RequiresAuthentication
	public ApiResult<?> checkLogin() {
		return ApiResult.success();
	}


    @ApiOperation("检查是否显示图标")
    @GetMapping ("/validate/iocn")
    public ApiResult<?> checkIocn() {
        User user = WebUtils.user();
        IocnDTO iocnDTO = new IocnDTO();
        if (null != user){
            if("53159fb44b8711ed93aa0242ac110002".equals(user.getId())){
                iocnDTO.setIsShow(true);
                iocnDTO.setPhone("联系电话: 13638501752");
                iocnDTO.setName("技术支持: 贵州超能科技有限公司");
                return ApiResult.success(iocnDTO);
            }
        }
        return ApiResult.success();
    }
}
